In [ ]:
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import warnings
warnings.filterwarnings("ignore")
from statistics import mean
import os
from sklearn.preprocessing import MinMaxScaler
import xgboost as xgb
from sklearn.model_selection import train_test_split
from sklearn.metrics import accuracy_score
from sklearn.preprocessing import LabelEncoder
from keras.utils import to_categorical
from keras.models import Sequential
from keras.layers import Dense, LSTM
from sklearn.feature_selection import RFE
from sklearn.linear_model import LinearRegression
In [ ]:
def scale_split(df):
    scaler = MinMaxScaler()
    numerical_columns = df.select_dtypes(include='number').columns
    #print(numerical_columns)
    scaled_df = df.copy()
    
    # positions = list(set(df['Pos']))
    
    # for role in positions:
        # role_data = df[df['Pos'] == role]
        # scaled_df.loc[scaled_df['Pos'] == role, numerical_columns] = scaler.fit_transform(role_data[numerical_columns])
    scaled_df[numerical_columns] = scaler.fit_transform(df[numerical_columns])
    non_numeric_columns = df.select_dtypes(exclude='number').columns
    #print(non_numeric_columns)
    scaled_df[non_numeric_columns] = df[non_numeric_columns]
    
    return scaled_df
In [ ]:
# directory containing the files
og_dir = 'c:\\Users\\advai\\College Semesters\\22-23 Win\\data-driven analysis of LCK\\Testing'
directory = os.path.join(og_dir, 'secret_regions_test')
models_directory = os.path.join(og_dir, 'model_files')

os.chdir(directory)
In [ ]:
positions = ["Top", "Jungle", "Middle", "ADC", "Support"]
In [ ]:
relevant_cols = [['K', 'A', 'KDA', 'KP', 'KS%', 'GD10', 'CSPM', 'DMG%', 'GOLD%', 'WPM'],
                 ['K', 'A', 'KDA', 'KP', 'KS%', 'DTH%', 'GD10', 'CSPM', 'WPM', 'WCPM'],
                 ['K', 'D', 'A', 'KDA', 'KS%', 'DTH%', 'GD10', 'CSPM', 'DMG%', 'WPM'],
                 ['K', 'D', 'A', 'KP', 'CSD10', 'DMG%', 'GOLD%', 'WPM', 'CWPM', 'WCPM'],
                 ['K', 'D', 'A', 'KDA', 'KS%', 'CSPM', 'DMG%', 'GOLD%', 'WPM', 'CWPM']]
for role in positions:
    print("for", role)
    print(relevant_cols[positions.index(role)])
for Top
['K', 'A', 'KDA', 'KP', 'KS%', 'GD10', 'CSPM', 'DMG%', 'GOLD%', 'WPM']
for Jungle
['K', 'A', 'KDA', 'KP', 'KS%', 'DTH%', 'GD10', 'CSPM', 'WPM', 'WCPM']
for Middle
['K', 'D', 'A', 'KDA', 'KS%', 'DTH%', 'GD10', 'CSPM', 'DMG%', 'WPM']
for ADC
['K', 'D', 'A', 'KP', 'CSD10', 'DMG%', 'GOLD%', 'WPM', 'CWPM', 'WCPM']
for Support
['K', 'D', 'A', 'KDA', 'KS%', 'CSPM', 'DMG%', 'GOLD%', 'WPM', 'CWPM']

We now use this ensemble model as the final piece of our rankings. We will take the ranking achieved from this, and the ranking achieved from raw %ile in each of the important stats for a given role, to create a final ranking for players by their respective role

In [ ]:
# now ranking the Spring 2023 roster data
os.chdir(os.path.join(og_dir, "secret_regions_test"))

player_data = pd.read_csv('LEC 2022 Spring.csv')
mvp_data = pd.read_csv('lec_mvp.csv')

os.chdir(os.path.join(og_dir, "model_files"))
# create a new column called "MVP" in the player_data dataframe
player_data["MVP"] = 0

# iterate over each row in the MVP data dataframe
for index, row in mvp_data.iterrows():
    # check if the player's name exists in the player_data dataframe
    if row["Player"] in player_data["Player"].values:
        # if so, find the row with the player's name and update the "MVP" column with the MVP points
        player_data.loc[player_data["Player"] == row["Player"], "MVP"] = row["Points"]

player_data['Year'] = "2023"
player_data['Season'] = "Spring"

exclude = ['Player', 'Team', 'Pos', 'Year', 'Season']
incldue = [col for col in player_data.columns if col not in exclude]
for cols in incldue:
    for idx, val in player_data[cols].items():
        if str(val).endswith("%"):
            player_data.at[idx, cols] = str(val.strip("%"))

player_data[incldue] = player_data[incldue].astype('float64')

rank_test = scale_split(player_data)
rank_test = rank_test.dropna(axis=1)
rank_test_vals = rank_test.select_dtypes(include='number')
rank_test_vals = rank_test_vals.drop(['GP', 'MVP'], axis=1)
rank_test_labels = rank_test.select_dtypes(exclude='number')
rank_test_labels = pd.concat([rank_test_labels, rank_test[['GP', 'MVP']]], axis=1)

role_rank_test = []
role_rank_test_labels = []
role_rank_test_vals = []
# generating 5 sets of data for players in each role
for position in positions:
    role_rank_test.append(rank_test[rank_test['Pos'] == position])
    role_rank_test_labels.append(rank_test_labels[rank_test_labels['Pos'] == position])
    role_rank_test_vals.append(rank_test_vals[rank_test_labels['Pos'] == position])
    
role_rank_test[positions.index("ADC")].sort_values(by=['KDA', 'W%', 'DMG%'], ascending=False).head()
Out[ ]:
Player Team Pos GP W% CTR% K D A KDA ... D%P15 EGPM GOLD% STL WPM CWPM WCPM MVP Year Season
45 Upset Fnatic ADC 1.0 0.901639 0.576923 0.812500 0.000000 0.377622 1.000000 ... 0.856618 0.908046 0.878641 0.00 0.120253 0.103448 0.473684 0.1 2023 Spring
8 Comp Rogue ADC 1.0 1.000000 0.461538 0.906250 0.268657 0.398601 0.337838 ... 0.860294 1.000000 0.966019 0.00 0.126582 0.172414 0.526316 0.4 2023 Spring
12 Flakked G2 Esports ADC 1.0 0.721311 0.461538 0.687500 0.313433 0.307692 0.222973 ... 0.941176 0.835249 0.873786 0.00 0.107595 0.137931 0.578947 0.1 2023 Spring
44 UNF0RGIVEN MAD Lions ADC 1.0 0.442623 0.903846 0.843750 0.402985 0.293706 0.195946 ... 0.941176 0.873563 0.932039 0.00 0.018987 0.051724 0.289474 0.1 2023 Spring
18 Jezu SK Gaming ADC 1.0 0.360656 0.692308 0.729167 0.373134 0.160839 0.155405 ... 0.856618 0.747126 0.878641 0.25 0.075949 0.189655 0.394737 0.2 2023 Spring

5 rows × 31 columns

In [ ]:
def rankings(role_rank_test, relevant_cols, positions):
    ranks = {}
    for role in positions:
        # print(role)
        relevant = relevant_cols[positions.index(role)]
        # print(relevant)
        rankings_dict = {}
        temp_data = role_rank_test[positions.index(role)]
        
        for player in temp_data["Player"]:
            player_rankings = []
            for col in list(relevant):
                # print(col, "\n")
                sorted_data = temp_data.sort_values(by=col, ascending=(col in ["D"])).reset_index()
                # print(sorted_data["Player"])
                player_rank = sorted_data.index[sorted_data['Player'] == player].tolist()[0] + 1
                player_rankings.append(player_rank)
            rankings_dict[player] = mean(player_rankings)
        ranks[role] = rankings_dict
    return ranks
In [ ]:
percentile_ranks = rankings(role_rank_test, relevant_cols, positions)

# convert the float 'ranks' to actual ranks from 1 to 10/11
for role, players in percentile_ranks.items():
    # sort the players based on their scores in descending order
    sorted_players = sorted(players, key=players.get, reverse=False)
    # create a new dictionary to store the rankings
    rankings = {}
    # assign rankings to each player based on their position in the sorted list
    for i, player in enumerate(sorted_players):
        rankings[player] = i + 1
    # replace the original scores with the rankings
    percentile_ranks[role] = rankings
In [ ]:
def ensemble_rankings(args, ensemble_models, neural_net_models):
    role_rank_test = args[0]
    releveant_cols = args[1]
    positions = args[2]
    ranks = {}
    for role in positions:
        ensemble_model = ensemble_models[role]
        relevant = releveant_cols[positions.index(role)]
        rankings_dict = {}
        players = role_rank_test[positions.index(role)]["Player"]
        temp_data = role_rank_test[positions.index(role)][relevant]
        
        # augmenting with the nn stack
        temp_data_augmented = temp_data
        for key, value in neural_net_models.items(): # key is the model name, value is the dictionary
            role_fittings_for_nn = value 
            # role_fittings_for_nn is a dictionary with the role as the key
            # and the value is the corresponding model's name in disk
            
            # get the pre-trained neural model for the current role
            model_addr = role_fittings_for_nn[role]
            model = load_model(model_addr)
            # get the output of the keras neural model on the training data
            nn_output = model.predict(temp_data, verbose=0)
            
            # add the neural network output as a feature to the original training data
            temp_data_augmented = np.hstack((temp_data_augmented, nn_output))
        
        # predict with ensemble model
        predictions = ensemble_model.predict(temp_data_augmented)
        rankings_dict = {player: rank for player, rank in zip(players, predictions)}
        sorted_players = sorted(rankings_dict, key=rankings_dict.get, reverse=True)
        rankings = {}
        for i, player in enumerate(sorted_players):
            rankings[player] = i + 1
            
        ranks[role] = rankings
    return ranks
In [ ]:
from keras.models import load_model
from joblib import dump, load

testing_ensemble_args = [role_rank_test, relevant_cols, positions]
os.chdir(os.path.join(og_dir, 'model_files'))
top_ensem = load('Stacked_Ensemble_Top.joblib')
sup_ensem = load('Stacked_Ensemble_Support.joblib')
adc_ensem = load('Stacked_Ensemble_ADC.joblib')
mid_ensem = load('Stacked_Ensemble_Middle.joblib')
jgl_ensem = load('Stacked_Ensemble_Jungle.joblib')

ensemble_models = {
    'Top': top_ensem,
    'Support': sup_ensem,
    'ADC': adc_ensem,
    'Middle': mid_ensem,
    'Jungle': jgl_ensem
}
In [ ]:
nn_scaled = {'Basic LSTM': {'Support': 'Basic_LSTM_Support.keras',
  'Jungle': 'Basic_LSTM_Jungle.keras',
  'Top': 'Basic_LSTM_Top.keras',
  'Middle': 'Basic_LSTM_Middle.keras',
  'ADC': 'Basic_LSTM_ADC.keras'},
 'Basic LSTM with sigmoid acv fn': {'Support': 'Basic_LSTM_with_sigmoid_acv_fn_Support.keras',
  'Jungle': 'Basic_LSTM_with_sigmoid_acv_fn_Jungle.keras',
  'Top': 'Basic_LSTM_with_sigmoid_acv_fn_Top.keras',
  'Middle': 'Basic_LSTM_with_sigmoid_acv_fn_Middle.keras',
  'ADC': 'Basic_LSTM_with_sigmoid_acv_fn_ADC.keras'},
 'Stacked LSTM with dropout': {'Support': 'Stacked_LSTM_with_dropout_Support.keras',
  'Jungle': 'Stacked_LSTM_with_dropout_Jungle.keras',
  'Top': 'Stacked_LSTM_with_dropout_Top.keras',
  'Middle': 'Stacked_LSTM_with_dropout_Middle.keras',
  'ADC': 'Stacked_LSTM_with_dropout_ADC.keras'},
 'Convolution model': {'Support': 'Convolution_model_Support.keras',
  'Jungle': 'Convolution_model_Jungle.keras',
  'Top': 'Convolution_model_Top.keras',
  'Middle': 'Convolution_model_Middle.keras',
  'ADC': 'Convolution_model_ADC.keras'},
 'RNN Model': {'Support': 'RNN_Model_Support.keras',
  'Jungle': 'RNN_Model_Jungle.keras',
  'Top': 'RNN_Model_Top.keras',
  'Middle': 'RNN_Model_Middle.keras',
  'ADC': 'RNN_Model_ADC.keras'}}
In [ ]:
ensemble_ranks = ensemble_rankings(testing_ensemble_args, ensemble_models, nn_scaled)
In [ ]:
# now to get the MVP ranks
mvp_ranks = {}
for role in positions:
    temp_players = role_rank_test[positions.index(role)][["Player", "MVP"]]
    temp_players = temp_players.sort_values(by="MVP", ascending=False).reset_index()

    # create a new dictionary to store the rankings
    rankings = {}
    # assign rankings to each player based on their position in the sorted db
    for i, row in temp_players.iterrows():
        rankings[row["Player"]] = i + 1
    # replace the original scores with the rankings
    mvp_ranks[role] = rankings
In [ ]:
# combine the three ranks into one
final_evaluation = {}

for role in positions:
    mvp_rankings = mvp_ranks[role]
    ensemble_rankings = ensemble_ranks[role]
    percentile_rankings = percentile_ranks[role]

    # Combine the rankings using a suitable method, such as averaging
    combined_rankings = {}

    for player in mvp_rankings:
        # Compute the average rank of the player across the three structures
        avg_rank = (mvp_rankings[player] + ensemble_rankings[player] + percentile_rankings[player]) / 3

        # Add the player and their average rank to the combined rankings
        combined_rankings[player] = avg_rank
    sorted_ranks = sorted(combined_rankings, key=combined_rankings.get, reverse=False)
    rankings = {}
    for i, player in enumerate(sorted_ranks):
        rankings[player] = i + 1
        
    # Store the combined rankings for the position in the final_evaluation dictionary
    final_evaluation[role] = rankings
In [ ]:
final_evaluation
Out[ ]:
{'Top': {'BrokenBlade': 1,
  'Alphari': 2,
  'Odoamne': 3,
  'JNX': 4,
  'Armut': 5,
  'Finn': 6,
  'Wunder': 7,
  'Adam': 8,
  'HiRit': 9,
  'WhiteKnight': 10},
 'Jungle': {'Elyoya': 1,
  'Cinkrof': 2,
  'Razork': 3,
  'Malrang': 4,
  'Markoon': 5,
  'Selfmade': 6,
  'Jankos': 7,
  'Zanzarah': 8,
  'Gilius': 9,
  'Shlatan': 10},
 'Middle': {'Larssen': 1,
  'Vetheo': 2,
  'Humanoid': 3,
  'Perkz': 4,
  'Caps': 5,
  'Sertuss': 6,
  'Dajor': 7,
  'Nukeduck': 8,
  'Reeker': 9,
  'nuc': 10},
 'ADC': {'Comp': 1,
  'Neon': 2,
  'Upset': 3,
  'Patrik': 4,
  'Flakked': 5,
  'Jezu': 6,
  'Kobbe': 7,
  'Carzzy': 8,
  'UNF0RGIVEN': 9,
  'xMatty': 10},
 'Support': {'Hylissang': 1,
  'Trymbi': 2,
  'Mikyx': 3,
  'Targamas': 4,
  'promisq': 5,
  'Kaiser': 6,
  'LIMIT': 7,
  'Treatz': 8,
  'Advienne': 9,
  'Mersa': 10,
  'Labrov': 11}}
In [ ]:
# Working on polar graphs for Given player vs Rank 1 Player or any given Player
import plotly.graph_objects as go

# data for the radar chart

player_name = "promisq" #promisq more internationals than <x>
comparison = 1 # rank of the player to be compared with, default 1
comparison_name = "" # name of the player. ideally, feed either or
# get the row for the player from the DataFrame
player_row = player_data[player_data["Player"] == player_name]

player_role = player_row["Pos"].iloc[0]
polar_relevant = relevant_cols[positions.index(player_role)]
for key, value in final_evaluation[player_role].items():
    if value == comparison:
        comparison_name = key
comaprison_row = player_data[player_data["Player"] == comparison_name]


player_percentiles = []
comparison_percentiles = []
max_percentiles = [1 for col in polar_relevant]
# Get the percentiles for the player's role
role_data = player_data[player_data["Pos"] == player_role]
for col in polar_relevant:
    max_val = role_data[col].max()
    player_val = player_row[col].iloc[0]
    player_percentiles.append(player_val / max_val)
    comp_val = comaprison_row[col].iloc[0]
    comparison_percentiles.append(comp_val / max_val)
# get the list of all players with the same "Pos"
# For col in relevant cols ->
    # sort them by col, then take greatest value in the given col and value of the given player
    # store the percentage values for given player (basically just the ratio)
    # do the same for the comparison player, and store in the separate list

fig = go.Figure()

# add the max values to set the background
fig.add_trace(go.Scatterpolar(
      r=max_percentiles,
      theta=list(polar_relevant),
      fill='toself',
      name='Max Value amongst Players'
))

# add the player's data to the chart
fig.add_trace(go.Scatterpolar(
      r=player_percentiles,
      theta=list(polar_relevant),
      fill='toself',
      name='Player Scores for ' + player_name
))

# add the comparison percentiles to the chart
fig.add_trace(go.Scatterpolar(
      r=comparison_percentiles,
      theta=list(polar_relevant),
      fill='toself',
      name='Scores for rank ' + str(comparison) + ' : ' + comparison_name
))

# customize the layout of the chart
fig.update_layout(
    polar=dict(
        radialaxis=dict(
            visible=True,
            range=[0, 1]
        )
    ),
    showlegend=True
)

# show the chart
fig.show(renderer='notebook')

Real Ranks :

First : Odo,        Malrang,        Vethro, Upset, Hyli

Second : BB,        Jankos (Aware), Umanoid, Comp, Trymbi

Third : Wunder (xdd),Elyoya,        Larssen, Patrik, Targamas

Our Ranks :

First : BB,       Elyoya,  Larssen, Comp, Hyli

Second : Alphari, Cinkrof, Vetheo,  Neon, Trymbi

Third : Odo,      Razork,  Umanoid, Upset, MickeyXdd

Top : Odo, BB check. Wunder 7th OMEGALUL

Jgl : Elyoya check. Malrang 4th, Juankos 7th xddDespair

Mid : Larssen, Vetheo, Umanoid check, but Umanoid > vetheo/larssen

Bot : Upset was upset by comp and neon. Patrik 4th

Supp : Hyli kingdom. Trymbi correct, Targamas 4th, mikyxdd replaces

In [ ]:
# now for NA, gotta make it fast, they have a plane to catch
# now ranking the Spring 2023 roster data
os.chdir(os.path.join(og_dir, "secret_regions_test"))

player_data = pd.read_csv('LCS 2023 Spring.csv')
mvp_data = pd.read_csv('lcs_mvp.csv')

os.chdir(os.path.join(og_dir, "model_files"))
# create a new column called "MVP" in the player_data dataframe
player_data["MVP"] = 0

# iterate over each row in the MVP data dataframe
for index, row in mvp_data.iterrows():
    # check if the player's name exists in the player_data dataframe
    if row["Player"] in player_data["Player"].values:
        # if so, find the row with the player's name and update the "MVP" column with the MVP points
        player_data.loc[player_data["Player"] == row["Player"], "MVP"] = row["Points"]

player_data['Year'] = "2023"
player_data['Season'] = "Spring"

exclude = ['Player', 'Team', 'Pos', 'Year', 'Season']
incldue = [col for col in player_data.columns if col not in exclude]
for cols in incldue:
    for idx, val in player_data[cols].items():
        if str(val).endswith("%"):
            player_data.at[idx, cols] = str(val.strip("%"))

player_data[incldue] = player_data[incldue].astype('float64')

rank_test = scale_split(player_data)
rank_test = rank_test.dropna(axis=1)
rank_test_vals = rank_test.select_dtypes(include='number')
rank_test_vals = rank_test_vals.drop(['GP', 'MVP'], axis=1)
rank_test_labels = rank_test.select_dtypes(exclude='number')
rank_test_labels = pd.concat([rank_test_labels, rank_test[['GP', 'MVP']]], axis=1)

role_rank_test = []
role_rank_test_labels = []
role_rank_test_vals = []
# generating 5 sets of data for players in each role
for position in positions:
    role_rank_test.append(rank_test[rank_test['Pos'] == position])
    role_rank_test_labels.append(rank_test_labels[rank_test_labels['Pos'] == position])
    role_rank_test_vals.append(rank_test_vals[rank_test_labels['Pos'] == position])
    
role_rank_test[positions.index("ADC")].sort_values(by=['KDA', 'W%', 'DMG%'], ascending=False).head()
Out[ ]:
Player Team Pos GP W% CTR% K D A KDA ... D%P15 EGPM GOLD% STL WPM CWPM WCPM MVP Year Season
2 Berserker Cloud9 ADC 0.947368 0.79 0.42 0.836538 0.253731 0.489474 0.933333 ... 0.807432 0.963504 0.946341 0.0 0.159664 0.282051 0.551020 0.500000 2023 Spring
37 Prince FlyQuest ADC 0.947368 0.74 0.63 0.971154 0.447761 0.389474 0.504762 ... 0.922297 1.000000 0.985366 0.0 0.243697 0.307692 0.775510 0.833333 2023 Spring
18 FBI Evil Geniuses ADC 0.947368 0.53 0.53 0.903846 0.522388 0.478947 0.457143 ... 0.952703 0.879562 0.941463 0.0 0.134454 0.230769 0.571429 0.166667 2023 Spring
32 Luger Counter Logic Gaming ADC 0.947368 0.53 0.58 0.673077 0.447761 0.410526 0.428571 ... 0.658784 0.813869 0.868293 0.2 0.033613 0.076923 0.632653 0.333333 2023 Spring
15 Doublelift 100 Thieves ADC 1.000000 0.60 0.55 1.000000 0.686567 0.531579 0.380952 ... 0.956081 0.923358 0.995122 0.0 0.109244 0.179487 0.775510 1.000000 2023 Spring

5 rows × 31 columns

In [ ]:
percentile_ranks = rankings(role_rank_test, relevant_cols, positions)

# convert the float 'ranks' to actual ranks from 1 to 10/11
for role, players in percentile_ranks.items():
    # sort the players based on their scores in descending order
    sorted_players = sorted(players, key=players.get, reverse=False)
    # create a new dictionary to store the rankings
    rankings = {}
    # assign rankings to each player based on their position in the sorted list
    for i, player in enumerate(sorted_players):
        rankings[player] = i + 1
    # replace the original scores with the rankings
    percentile_ranks[role] = rankings

testing_ensemble_args = [role_rank_test, relevant_cols, positions]

ensemble_ranks = ensemble_rankings(testing_ensemble_args, ensemble_models, nn_scaled)

# now to get the MVP ranks
mvp_ranks = {}
for role in positions:
    temp_players = role_rank_test[positions.index(role)][["Player", "MVP"]]
    temp_players = temp_players.sort_values(by="MVP", ascending=False).reset_index()

    # create a new dictionary to store the rankings
    rankings = {}
    # assign rankings to each player based on their position in the sorted db
    for i, row in temp_players.iterrows():
        rankings[row["Player"]] = i + 1
    # replace the original scores with the rankings
    mvp_ranks[role] = rankings

# combine the three ranks into one
final_evaluation = {}

for role in positions:
    mvp_rankings = mvp_ranks[role]
    ensemble_rankings = ensemble_ranks[role]
    percentile_rankings = percentile_ranks[role]

    # Combine the rankings using a suitable method, such as averaging
    combined_rankings = {}

    for player in mvp_rankings:
        # Compute the average rank of the player across the three structures
        avg_rank = (mvp_rankings[player] + ensemble_rankings[player] + percentile_rankings[player]) / 3

        # Add the player and their average rank to the combined rankings
        combined_rankings[player] = avg_rank
    sorted_ranks = sorted(combined_rankings, key=combined_rankings.get, reverse=False)
    rankings = {}
    for i, player in enumerate(sorted_ranks):
        rankings[player] = i + 1
        
    # Store the combined rankings for the position in the final_evaluation dictionary
    final_evaluation[role] = rankings
In [ ]:
final_evaluation
Out[ ]:
{'Top': {'Fudge': 1,
  'Dhokla': 2,
  'Summit': 3,
  'Impact': 4,
  'Ssumday': 5,
  'Armut': 6,
  'Revenge': 7,
  'Hauntzer': 8,
  'Solo': 9,
  'Tenacity': 10,
  'Licorice': 11},
 'Jungle': {'Spica': 1,
  'Blaber': 2,
  'Pyosik': 3,
  'Closer': 4,
  'Inspired': 5,
  'River': 6,
  'Contractz': 7,
  'Bugi': 8,
  'Kenvi': 9,
  'Santorin': 10},
 'Middle': {'VicLa': 1,
  'Gori': 2,
  'EMENES': 3,
  'jojopyun': 4,
  'Palafox': 5,
  'Maple': 6,
  'Bjergsen': 7,
  'Jensen': 8,
  'Haeri': 9,
  'ry0ma': 10,
  'Bolulu': 11,
  'Ablazeolive': 12,
  'Diplex': 13,
  'Young': 14},
 'ADC': {'Doublelift': 1,
  'Prince': 2,
  'Berserker': 3,
  'FBI': 4,
  'WildTurtle': 5,
  'Yeon': 6,
  'Luger': 7,
  'Stixxay': 8,
  'Neo': 9,
  'Tactical': 10,
  'Tomo': 11,
  'Spawn': 12},
 'Support': {'huhi': 1,
  'Busio': 2,
  'CoreJJ': 3,
  'Vulcan': 4,
  'Fleshy': 5,
  'Zven': 6,
  'Chime': 7,
  'Winsome': 8,
  'Poome': 9,
  'Eyla': 10,
  'Biofrost': 11,
  'IgNar': 12}}

Real ranks :

First : Fudge factor, Crabber,  Gori, Zerker,       Vulcan

Second : Impact,      Spica,    EMENES, Prince xdd, Zven

Third : Ssumday,      Inspired, VicLa, DL,          Huhi

Model Ranks :

First : Fudge factor, Spica,            VicLa,  DL,     Huhi

Second : Big Dhokes, Crabber,           Gori,   Prince, Busio

Third : Summit,     World Champ Pyosik, EMENES, Zerker, CoreJJ

Top has big chnages, Impact Ssumday are 4-5

Jungle -> Inspired comes 5th

Mid -> Same 3, but order

ADC -> same 3, order

Supp -> Vulcan is 4th, Zven is 6th

In [ ]:
#Quick LPL test, but a lot of features are unavailable for their data
# FB%, GD@10, CSD@10 changed to EGPM for GD@10 and CPSPM for CSD@10. FB% is not used
relevant_lpls = [['K', 'A', 'KDA', 'KP', 'KS%', 'EGPM', 'CSPM', 'DMG%', 'GOLD%', 'WPM'],
                 ['K', 'A', 'KDA', 'KP', 'KS%', 'DTH%', 'EGPM', 'CSPM', 'WPM', 'WCPM'],
                 ['K', 'D', 'A', 'KDA', 'KS%', 'DTH%', 'EGPM', 'CSPM', 'DMG%', 'WPM'],
                 ['K', 'D', 'A', 'KP', 'CSPM', 'DMG%', 'GOLD%', 'WPM', 'CWPM', 'WCPM'],
                 ['K', 'D', 'A', 'KDA', 'KS%', 'CSPM', 'DMG%', 'GOLD%', 'WPM', 'CWPM']]
In [ ]:
# now ranking the Spring 2023 roster data
os.chdir(os.path.join(og_dir, "secret_regions_test"))

player_data = pd.read_csv('LPL 2023 Spring.csv')
mvp_data = pd.read_csv('lpl_mvp.csv')

os.chdir(os.path.join(og_dir, "model_files"))
# create a new column called "MVP" in the player_data dataframe
player_data["MVP"] = 0

# iterate over each row in the MVP data dataframe
for index, row in mvp_data.iterrows():
    # check if the player's name exists in the player_data dataframe
    if row["Player"] in player_data["Player"].values:
        # if so, find the row with the player's name and update the "MVP" column with the MVP points
        player_data.loc[player_data["Player"] == row["Player"], "MVP"] = row["Points"]

player_data['Year'] = "2023"
player_data['Season'] = "Spring"

exclude = ['Player', 'Team', 'Pos', 'Year', 'Season']
incldue = [col for col in player_data.columns if col not in exclude]
for cols in incldue:
    for idx, val in player_data[cols].items():
        if str(val).endswith("%"):
            player_data.at[idx, cols] = str(val.strip("%"))

player_data[incldue] = player_data[incldue].astype('float64')

rank_test = scale_split(player_data)
rank_test = rank_test.dropna(axis=1)
rank_test_vals = rank_test.select_dtypes(include='number')
rank_test_vals = rank_test_vals.drop(['GP', 'MVP'], axis=1)
rank_test_labels = rank_test.select_dtypes(exclude='number')
rank_test_labels = pd.concat([rank_test_labels, rank_test[['GP', 'MVP']]], axis=1)

role_rank_test = []
role_rank_test_labels = []
role_rank_test_vals = []
# generating 5 sets of data for players in each role
for position in positions:
    role_rank_test.append(rank_test[rank_test['Pos'] == position])
    role_rank_test_labels.append(rank_test_labels[rank_test_labels['Pos'] == position])
    role_rank_test_vals.append(rank_test_vals[rank_test_labels['Pos'] == position])
    
role_rank_test[positions.index("ADC")].sort_values(by=['KDA', 'W%', 'DMG%'], ascending=False).head()
Out[ ]:
Player Team Pos GP W% CTR% K D A KDA ... DPM DMG% EGPM GOLD% WPM CWPM WCPM MVP Year Season
72 Ruler JD Gaming ADC 0.853659 0.78 0.47 0.773148 0.246575 0.434679 1.000000 ... 0.784441 0.711462 1.000000 0.940 0.197917 0.313725 0.750000 0.529412 2023 Spring
50 Light Weibo Gaming ADC 0.926829 0.64 0.54 0.814815 0.390411 0.453682 0.646341 ... 0.784441 0.802372 0.935361 0.960 0.140625 0.117647 0.613636 0.176471 2023 Spring
51 LP LNG Esports ADC 0.926829 0.72 0.38 0.939815 0.534247 0.548694 0.560976 ... 0.867099 0.830040 0.897338 0.895 0.166667 0.156863 0.727273 0.117647 2023 Spring
37 huanfeng ThunderTalk Gaming ADC 0.853659 0.50 0.61 0.611111 0.342466 0.334917 0.536585 ... 0.658023 0.723320 0.828897 0.900 0.177083 0.196078 0.522727 0.176471 2023 Spring
22 Elk Bilibili Gaming ADC 1.000000 0.60 0.45 1.000000 0.609589 0.501188 0.475610 ... 1.000000 1.000000 0.950570 0.975 0.156250 0.156863 0.727273 0.352941 2023 Spring

5 rows × 24 columns

In [ ]:
percentile_ranks = rankings(role_rank_test, relevant_lpls, positions)

# convert the float 'ranks' to actual ranks from 1 to 10/11
for role, players in percentile_ranks.items():
    # sort the players based on their scores in descending order
    sorted_players = sorted(players, key=players.get, reverse=False)
    # create a new dictionary to store the rankings
    rankings = {}
    # assign rankings to each player based on their position in the sorted list
    for i, player in enumerate(sorted_players):
        rankings[player] = i + 1
    # replace the original scores with the rankings
    percentile_ranks[role] = rankings

testing_ensemble_args = [role_rank_test, relevant_lpls, positions]

ensemble_ranks = ensemble_rankings(testing_ensemble_args, ensemble_models, nn_scaled)

# now to get the MVP ranks
mvp_ranks = {}
for role in positions:
    temp_players = role_rank_test[positions.index(role)][["Player", "MVP"]]
    temp_players = temp_players.sort_values(by="MVP", ascending=False).reset_index()

    # create a new dictionary to store the rankings
    rankings = {}
    # assign rankings to each player based on their position in the sorted db
    for i, row in temp_players.iterrows():
        rankings[row["Player"]] = i + 1
    # replace the original scores with the rankings
    mvp_ranks[role] = rankings

# combine the three ranks into one
final_evaluation = {}

for role in positions:
    mvp_rankings = mvp_ranks[role]
    ensemble_rankings = ensemble_ranks[role]
    percentile_rankings = percentile_ranks[role]

    # Combine the rankings using a suitable method, such as averaging
    combined_rankings = {}

    for player in mvp_rankings:
        # Compute the average rank of the player across the three structures
        avg_rank = (mvp_rankings[player] + ensemble_rankings[player] + percentile_rankings[player]) / 3

        # Add the player and their average rank to the combined rankings
        combined_rankings[player] = avg_rank
    sorted_ranks = sorted(combined_rankings, key=combined_rankings.get, reverse=False)
    rankings = {}
    for i, player in enumerate(sorted_ranks):
        rankings[player] = i + 1
        
    # Store the combined rankings for the position in the final_evaluation dictionary
    final_evaluation[role] = rankings
In [ ]:
final_evaluation
Out[ ]:
{'Top': {'shanji': 1,
  'Ale': 2,
  'YSKM': 3,
  'Zika': 4,
  'TheShy': 5,
  'Breathe': 6,
  'Bin': 7,
  'Xiaoxu': 8,
  '369': 9,
  'Invincible': 10,
  'Zdz': 11,
  'Wayward': 12,
  'Cube': 13,
  'Biubiu': 14,
  'Qingtian': 15,
  'Hery': 16,
  'neny': 17,
  'HOYA': 18,
  'Xiaolaohu': 19,
  'Rich': 20,
  'fearness': 21},
 'Jungle': {'Kanavi': 1,
  'Jiejie': 2,
  'Karsa': 3,
  'Tarzan': 4,
  'Leyan': 5,
  'Beichuan': 6,
  'Tian': 7,
  'Heng': 8,
  'Wei': 9,
  'Ning': 10,
  'Xun': 11,
  'Aki': 12,
  'Xiaohao': 13,
  'Meteor': 14,
  'XLB': 15,
  'shad0w': 16,
  'haoye': 17,
  'H4cker': 18,
  'gideon': 19},
 'Middle': {'Scout': 1,
  'Xiaohu': 2,
  'Rookie': 3,
  'Shanks': 4,
  'FoFo': 5,
  'knight': 6,
  'Yagao': 7,
  'Creme': 8,
  'Care': 9,
  'ucal': 10,
  'pinz': 11,
  'Angel': 12,
  'Strive': 13,
  'neny': 14,
  'Dove': 15,
  'Qing': 16,
  'haichao': 17,
  'Pout': 18,
  'Forge': 19,
  'Dream': 20,
  'Harder': 21,
  'xqw': 22,
  'Tangyuan': 23},
 'ADC': {'Elk': 1,
  'JackeyLove': 2,
  'Ruler': 3,
  'Able': 4,
  'LP': 5,
  'GALA': 6,
  'Hope': 7,
  'Light': 8,
  'Doggo': 9,
  'Ahn': 10,
  'Photic': 11,
  'Lwx': 12,
  'Leave': 13,
  'Betty': 14,
  'Assum': 15,
  'Lpc': 16,
  'huanfeng': 17},
 'Support': {'Iwandy': 1,
  'Wink': 2,
  'Missing': 3,
  'Zhuo': 4,
  'ON': 5,
  'Meiko': 6,
  'Crisp': 7,
  'Jinjiao': 8,
  'ppgod': 9,
  'Mark': 10,
  'Ming': 11,
  'Hang': 12,
  'yaoyao': 13,
  'Baolan': 14,
  'XinLiu': 15,
  'Lele': 16,
  'QiuQiu': 17,
  'Bunny': 18,
  'Southwind': 19,
  'SwordArt': 20,
  'Jerry': 21,
  'bkr': 22}}

Real Ranks :

First : 369, JieJie, Scout, Ruler, Meiko

Second : Ale, Kanavi, Knight, Elk, Missing

Thrid : Shanji, Tarzan, FoFo, Leave, Hang

Model Ranks :

First : Shanji, Kanavi, Scout, Elk, Iwandy

Second : Ale, JieJie, Xiaohu, JKL, Wink

Third : YSKM, Karsa, Cookie, Ruler, Missing

top -> 369 rolled a 9 :( TheSHY is 5th even after all that inting, my man

jgl -> Tarzan close 4th

Mid -> fofo, knight 5-6, shanks on 4

ADC -> xdd JKL, dear god leave is 13th??

Supp -> Meiko on 6, Hang on 12th?

(keep in mind its the model doing this)